package com.furentech.iotserver.fa.sinopec.sinopec_processor;


import com.alibaba.fastjson.JSON;
import com.furentech.iotserver.fa.server.ChannelUtil;
import com.furentech.iotserver.fa.sinopec.SinopecFunCode;
import com.furentech.iotserver.fa.utils.NumberUtil;
import com.furentech.iotserver.fa.utils.HexStringUtils;
import io.netty.channel.Channel;
import lombok.Data;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Component;

@Data
class TranData
{
    long POS_TTC;
    String T_TYPE;
    String TIME;
    String ASN;
    long BAL;
    int AMN;
    int CTC;
    String TAC;
    String GMAC;
    String PSAM_TAC;
    String PSAM_ASN;
    String PSAM_TID;
    String PSAM_TTC;
    int DS;
    String UNIT;
    String C_TYPE;
    String VER;
    int NZN;
    String G_CODE;
    int VOL;
    int PRC;
    int EMP;
    long V_TOT;
    String RFU;
    String NozUp;
    String ValveOpen;
    String ValveClose;
    String NozDown;
    String AvrFlowrate;
    String MaxFlowrate;
    int SettleType;
    int attendant;
    String PaymentMothd;
    String UUID;
    String RFU1;
    String T_MAC;
}

@Component
public class TranData_Processor extends SinopecProcessorBase {

    private final static Logger logger = LoggerFactory.getLogger(TranData_Processor.class);
    TranData decodeFormBytes(byte[] buf)
    {
        if (buf.length < 196) {
            logger.warn("buf数据长度不够，不能从buf中解析出完整的TranData对象");
            return null;
        }
        TranData tranData = new TranData();

        tranData.setPOS_TTC(NumberUtil.byte2intBE(buf, 1, 4));
        tranData.setT_TYPE(String.format("0x%02x", buf[5]));
        tranData.setTIME(HexStringUtils.toHexString(buf, 6, 7));
        tranData.setASN(HexStringUtils.toHexString(buf, 13, 10));

        tranData.setBAL(NumberUtil.byte2intBE(buf, 23, 4));
        tranData.setAMN((int)NumberUtil.byte2intBE(buf, 27, 3));
        tranData.setCTC((int)NumberUtil.byte2intBE(buf, 30, 2));

        tranData.setTAC(HexStringUtils.toHexString(buf, 32, 4));
        tranData.setGMAC(HexStringUtils.toHexString(buf, 36, 4));
        tranData.setPSAM_TAC(HexStringUtils.toHexString(buf, 40, 4));
        tranData.setPSAM_ASN(HexStringUtils.toHexString(buf, 44, 10));
        tranData.setPSAM_TID(HexStringUtils.toHexString(buf, 54, 6));
        tranData.setPSAM_TTC(HexStringUtils.toHexString(buf, 60, 4));

        tranData.setDS(buf[64]);
        tranData.setUNIT(String.format("0x%02x",buf[65]));
        tranData.setC_TYPE(String.format("0x%02x",buf[66]));
        tranData.setVER(String.format("0x%02x", buf[67]));
        tranData.setNZN(buf[68]);
        tranData.setG_CODE(String.format("0x%s", HexStringUtils.toHexString(buf, 69, 2)));

        tranData.setVOL((int)NumberUtil.byte2intBE(buf, 71, 3));

        tranData.setPRC((int)NumberUtil.byte2intBE(buf, 74, 2));

        tranData.setEMP(buf[76]);
        tranData.setV_TOT(NumberUtil.byte2intBE(buf, 77, 4));

        tranData.setRFU(HexStringUtils.toHexString(buf, 81, 11));
        tranData.setNozUp(HexStringUtils.toHexString(buf, 92, 7));
        tranData.setValveOpen(HexStringUtils.toHexString(buf, 99, 7));
        tranData.setValveClose(HexStringUtils.toHexString(buf, 106, 7));
        tranData.setNozDown(HexStringUtils.toHexString(buf, 113, 7));
        tranData.setAvrFlowrate(String.format("%02x%02x.%02x", buf[120], buf[121], buf[122]));
        tranData.setMaxFlowrate(String.format("%02x%02x.%02x", buf[123], buf[124], buf[125]));

        tranData.setSettleType(buf[126]);
        tranData.setAttendant(buf[127]);
        tranData.setPaymentMothd(HexStringUtils.toHexString(buf, 128, 8));
        tranData.setUUID(HexStringUtils.toHexString(buf, 136, 32));
        tranData.setRFU1(HexStringUtils.toHexString(buf, 168, 24));
        tranData.setT_MAC(HexStringUtils.toHexString(buf, 192, 4));

        return tranData;
    }

    @Override
    String actualGetJsonString(byte[] buf) {
        TranData tranData = decodeFormBytes(buf);
        if (tranData == null) {
            return null;
        }
        return JSON.toJSONString(tranData);
    }

    @Override
    String actualGetReadableString(byte[] buf) {
        TranData tranData = decodeFormBytes(buf);
        if (tranData == null) {
            return null;
        }

        return String.format("交易流水号		:%d\r\n"+
                        "交易类型		:%s\r\n"+
                        "时间及日期		:%s\r\n"+
                        "卡应用号		:%s\r\n"+
                        "余额			:%8.2f\r\n"+
                        "实付金额		:%8.2f\r\n"+
                        "卡交易序号		:%d\r\n"+
                        "电子签名		:%s\r\n"+
                        "解灰认证码		:%s\r\n"+
                        "灰锁签名		:%s\r\n"+
                        "PSAM应用号		:%s\r\n"+
                        "PSAM编号		:%s\r\n"+
                        "PSAM-TTC		:%s\r\n"+
                        "扣款来源		:%d\r\n"+
                        "结算单位/方式	:%s\r\n"+
                        "卡类			:%s\r\n"+
                        "版本			:%s\r\n"+
                        "枪号			:%d\r\n"+
                        "油品代码		:%s\r\n"+
                        "升数			:%8.2f\r\n"+
                        "成交价格		:%8.2f\r\n"+
                        "员工号			:%d\r\n"+
                        "升累计			:%8.2f\r\n"+
                        "附加数据		:%s\r\n"+
                        "提枪时间		:%s\r\n"+
                        "开阀时间		:%s\r\n"+
                        "关阀时间		:%s\r\n"+
                        "挂枪时间		:%s\r\n"+
                        "平均流速		:%s\r\n"+
                        "最大流速		:%s\r\n"+
                        "定量方式		:%d\r\n"+
                        "服务员工号		:%d\r\n"+
                        "标准收款方式	:%s\r\n"+
                        "唯一订单码		:%s\r\n"+
                        "预留字段1		:%s\r\n"+
                        "终端数据认证码	:%s\r\n",
                tranData.POS_TTC,
                tranData.T_TYPE,
                tranData.TIME,
                tranData.ASN,
                (float)tranData.BAL/100,
                (float)tranData.AMN/100,
                tranData.CTC,
                tranData.TAC,
                tranData.GMAC,
                tranData.PSAM_TAC,
                tranData.PSAM_ASN,
                tranData.PSAM_TID,
                tranData.PSAM_TTC,
                tranData.DS,
                tranData.UNIT,
                tranData.C_TYPE,
                tranData.VER,
                tranData.NZN,
                tranData.G_CODE,
                (float)tranData.VOL/100,
                (float)tranData.PRC/100,
                tranData.EMP,
                (float)tranData.V_TOT/100,
                tranData.RFU,
                tranData.NozUp,
                tranData.ValveOpen,
                tranData.ValveClose,
                tranData.NozDown,
                tranData.AvrFlowrate,
                tranData.MaxFlowrate,
                tranData.SettleType,
                tranData.attendant,
                tranData.PaymentMothd,
                tranData.UUID,
                tranData.RFU1,
                tranData.T_MAC);
    }

    @Override
    byte[] actualGetResponse(byte[] buf, Channel channel) {

//        if (ChannelUtil.getCbRecordFlag(ChannelUtil.currentChannel)) {
//            ChannelUtil.setCbRecordFlag(ChannelUtil.currentChannel, false);
//            return null;
//        }

        byte[] resByteBuf = new byte[4];

        resByteBuf[0] = SinopecFunCode.CMD_ACK;
        resByteBuf[1] = buf[0];
        resByteBuf[2] = buf[68];
        resByteBuf[3] = 0x05;

        return resByteBuf;
    }
}
